defmodule TimeLib do
	@moduledoc false
	@day_sec 86400

	@week_map %{
		1 => "星期一",
		2 => "星期二",
		3 => "星期三",
		4 => "星期四",
		5 => "星期五",
		6 => "星期六",
		7 => "星期日",
	}

	def cur_year() do
		{{year, _, _}, _} = :calendar.local_time
		year
	end

	def cur_ymd() do
		{ymd, _} = :calendar.local_time
		ymd
	end

	@day_30 [2, 4, 6, 9, 11]
	@hms {0, 0, 0}
	def ym_first_last_day() do
		{{y, m, _d}, _} = :calendar.local_time
		t = cond do
			m == 2 ->
				case rem(y, 4) == 0 && rem(y, 100) != 0 do
					true ->
						{y, m, 29}
					_ ->
						{y, m, 28}
				end
			m in @day_30 ->
				{y, m, 30}
			true ->
				{y, m, 31}
		end
		{NaiveDateTime.from_erl!({{y, m, 1}, @hms}), NaiveDateTime.from_erl!({t, @hms})}
	end

	def default_min_date() do
		"0000-01-01 00:00:00"
		|> NaiveDateTime.from_iso8601!()
	end

	def default_max_date() do
		"9999-01-01 00:00:00"
		|> NaiveDateTime.from_iso8601!()
	end

	def now(),
			do: :calendar.local_time
					|> NaiveDateTime.from_erl!

	def now_string(),
			do: :calendar.local_time
					|> NaiveDateTime.from_erl!
					|> NaiveDateTime.to_string

	def today(),
			do: NaiveDateTime.local_now()
					|> get_date_zero()

	# yyyy-mm-dd
	def today_string(),
			do: :calendar.local_time
					|> NaiveDateTime.from_erl!
					|> NaiveDateTime.to_date
					|> to_string()

	def date_to_string(date) do
		date
		|> to_string()
	end

	def string_to_date(date_str) do
		case is_binary(date_str) && NaiveDateTime.from_iso8601(date_str) do
			{:ok, naive_date} ->
				naive_date
			_reason ->
				nil
		end
	end

	def ymd_to_date(ymd) do
		ymd <> " 00:00:00"
		|> NaiveDateTime.from_iso8601()
		|> case do
				 {:ok, date} ->
					 date
				 _ ->
					 false
			 end
	end

	def date_of_weekday(date_str) do
		int = string_to_date(date_str)
					|> Timex.weekday
		Map.get(@week_map, int)
	end

	def today_zero_string() do
		get_date_zero(NaiveDateTime.local_now())
		|> NaiveDateTime.to_string()
	end

	def today_zero_date() do
		get_date_zero(NaiveDateTime.local_now())
	end

	def add_day(date, day) do
		NaiveDateTime.add(date, day * @day_sec)
	end

	def after_day_zero(date, day) do
		add_day(date, day)
		|> get_date_zero()
	end

	def comp(ts1, ts2) when is_binary(ts1) and is_binary(ts2) do
		comp(string_to_date(ts1), string_to_date(ts2))
	end
	def comp(ts1, ts2) when is_binary(ts1) or is_binary(ts2) do

	end

	def ymd_h_str() do
		time = now()
		"#{time.year}-#{time.month}-#{time.day}_#{time.hour}"
	end

	def get_date_zero(date) do
		%NaiveDateTime{
			date |
			hour: 0,
			minute: 0,
			second: 0,
			microsecond: {0, 0}
		}
	end

	# 把秒转成 timer 里的system_time,定时器超时时间大小比较用
	# 1000 -> 1秒
	def to_system_time(mic_src) do
		:erlang.monotonic_time(1000000) + 1000 * mic_src
	end

	def ts() do
		%{
			year: year,
			month: month,
			day: day,
			hour: hour,
			minute: min,
			second: second,
			microsecond: {us, _precision},
		} = Timex.now("Etc/GMT+8")

	end


end
